/**
 * 
 */
package org.dragonfire.dasm.instr;

import java.util.HashMap;

import org.dragonfire.dasm.CompileException;
import org.dragonfire.dasm.postprocessor.Postprocessor;

/**
 * @author dandroid
 * @date Nov 30, 2006
 */
public abstract class Rule {

	private static HashMap<String, Rule> rules = new HashMap<String, Rule>();

	public abstract String evalParam(Postprocessor post, String bits);

	public static Rule getInstance(String name) {
		name = name.toUpperCase();
		if (!rules.containsKey(name))
			try {
				loadInternalRule(name + "Rule");
			} catch (Exception e) {
				throw new CompileException("ERROR_UNKNOWN_RULE", name);
			}
		return rules.get(name.toUpperCase());
	}

	public static void loadRule(String name) {
		try {
			Class rule = ClassLoader.getSystemClassLoader().loadClass(name);
			Rule d = (Rule) rule.newInstance();
			name = d.getClass().getSimpleName();
			name = name.replaceAll("(?i)(.*)rule", "$1");
			if (!rules.containsKey(name))
				rules.put(name, d);
			else
				throw new RuntimeException("Rule '" + name + "' already loaded.");
		} catch (ClassNotFoundException cnfe) {
			throw new IllegalArgumentException("Unknown rule '" + name + "'");
		} catch (Exception e) {
			if (e instanceof RuntimeException)
				throw (RuntimeException) e;
			throw new IllegalArgumentException("Error loading rule '" + name + "'");
		}
	}

	public static void loadInternalRule(String name) {
		loadRule("org.dragonfire.dasm.instr.rules." + name);
	}
}
